// 全局变量
let currentAnalysisData = null;
let currentLoginSession = null;
let loginPollingInterval = null;
const API_BASE = window.location.origin;

// DOM元素
const elements = {
    videoUrl: document.getElementById('videoUrl'),
    analyzeBtn: document.getElementById('analyzeBtn'),
    batchBtn: document.getElementById('batchBtn'),
    loadingSection: document.getElementById('loadingSection'),
    loadingText: document.getElementById('loadingText'),
    loadingSubtext: document.getElementById('loadingSubtext'),
    progressBar: document.getElementById('progressBar'),
    progressText: document.getElementById('progressText'),
    resultSection: document.getElementById('resultSection'),
    errorSection: document.getElementById('errorSection'),
    errorMessage: document.getElementById('errorMessage'),
    retryBtn: document.getElementById('retryBtn'),

    // 登录相关元素
    loginStatus: document.getElementById('loginStatus'),
    loginInfo: document.getElementById('loginInfo'),
    loginText: document.getElementById('loginText'),
    loginActions: document.getElementById('loginActions'),
    loginBtn: document.getElementById('loginBtn'),
    logoutBtn: document.getElementById('logoutBtn'),
    loginModal: document.getElementById('loginModal'),
    qrSection: document.getElementById('qrSection'),
    qrPlaceholder: document.getElementById('qrPlaceholder'),
    qrCode: document.getElementById('qrCode'),
    qrImage: document.getElementById('qrImage'),
    loginStatusSection: document.getElementById('loginStatusSection'),
    statusText: document.getElementById('statusText'),
    loginSuccessSection: document.getElementById('loginSuccessSection'),
    refreshQRBtn: document.getElementById('refreshQRBtn'),

    // 视频信息
    videoCover: document.getElementById('videoCover'),
    videoTitle: document.getElementById('videoTitle'),
    videoAuthor: document.getElementById('videoAuthor'),
    videoView: document.getElementById('videoView'),
    videoLike: document.getElementById('videoLike'),
    videoCoin: document.getElementById('videoCoin'),
    videoDuration: document.getElementById('videoDuration'),
    danmakuCount: document.getElementById('danmakuCount'),
    commentCount: document.getElementById('commentCount'),
    badgeSubtitle: document.getElementById('badgeSubtitle'),
    badgeFrames: document.getElementById('badgeFrames'),

    // 内容区域
    summaryContent: document.getElementById('summaryContent'),
    mindmapContent: document.getElementById('mindmapContent'),
    danmakuContent: document.getElementById('danmakuContent'),
    evaluationContent: document.getElementById('evaluationContent'),

    // 新增按钮
    recommendBtn: document.getElementById('recommendBtn'),
    seriesBtn: document.getElementById('seriesBtn'),

    // 原有按钮
    copyBtn: document.getElementById('copyBtn'),
    downloadBtn: document.getElementById('downloadBtn'),
    newAnalysisBtn: document.getElementById('newAnalysisBtn'),

    // 新增元素
    batchModal: document.getElementById('batchModal'),
    batchInput: document.getElementById('batchInput'),
    recommendationsSection: document.getElementById('recommendationsSection'),
    recommendationGrid: document.getElementById('recommendationGrid'),

    // 词云相关元素
    wordcloudSection: document.getElementById('wordcloudSection'),
    wordcloudCanvas: document.getElementById('wordcloudCanvas'),
    wordcloudLoading: document.getElementById('wordcloudLoading'),
    refreshWordcloudBtn: document.getElementById('refreshWordcloudBtn'),
    downloadWordcloudBtn: document.getElementById('downloadWordcloudBtn'),

    toast: document.getElementById('toast')
};

// 分析步骤配置
const ANALYSIS_STEPS = [
    { step: 1, text: '获取视频信息...', progress: 15 },
    { step: 2, text: '获取字幕和弹幕...', progress: 30 },
    { step: 3, text: '获取评论数据...', progress: 45 },
    { step: 4, text: '提取视频关键帧...', progress: 65 },
    { step: 4, text: 'AI深度分析中...', progress: 85 },
    { step: 4, text: '生成四大板块报告...', progress: 95 }
];

// ================ 事件监听器 ================
elements.analyzeBtn.addEventListener('click', handleAnalyze);
elements.retryBtn.addEventListener('click', handleAnalyze);
elements.newAnalysisBtn.addEventListener('click', resetToInput);
elements.copyBtn.addEventListener('click', copyToClipboard);
elements.downloadBtn.addEventListener('click', downloadReport);

// 新增功能事件监听器
elements.batchBtn.addEventListener('click', openBatchModal);
elements.recommendBtn?.addEventListener('click', getRecommendations);
elements.seriesBtn?.addEventListener('click', analyzeSeries);

// 登录功能事件监听器
elements.loginBtn?.addEventListener('click', openLoginModal);
elements.logoutBtn?.addEventListener('click', handleLogout);
elements.refreshQRBtn?.addEventListener('click', refreshQRCode);

// 词云功能事件监听器
elements.refreshWordcloudBtn?.addEventListener('click', refreshWordcloud);
elements.downloadWordcloudBtn?.addEventListener('click', downloadWordcloud);

// 示例链接点击
document.querySelectorAll('.example-link').forEach(link => {
    link.addEventListener('click', (e) => {
        e.preventDefault();
        elements.videoUrl.value = e.target.dataset.url;
        elements.videoUrl.focus();
    });
});

// 标签页切换
document.querySelectorAll('.tab-btn').forEach(btn => {
    btn.addEventListener('click', () => {
        const tabName = btn.dataset.tab;
        switchTab(tabName);
    });
});

// 回车键触发分析
elements.videoUrl.addEventListener('keypress', (e) => {
    if (e.key === 'Enter') {
        handleAnalyze();
    }
});

// ================ 主要功能函数 ================
async function handleAnalyze() {
    const url = elements.videoUrl.value.trim();
    
    if (!url) {
        showToast('请输入B站视频链接', 'error');
        elements.videoUrl.focus();
        return;
    }

    // 验证URL格式
    if (!url.includes('bilibili.com') && !url.includes('b23.tv') && !url.startsWith('BV')) {
        showToast('请输入有效的B站视频链接或BV号', 'error');
        return;
    }

    showLoading();
    
    try {
        // 模拟进度更新
        simulateProgress();
        
        // 调用分析API
        const response = await fetch(`${API_BASE}/api/analyze`, {
            method: 'POST',
            headers: {
                'Content-Type': 'application/json'
            },
            body: JSON.stringify({ url })
        });

        const result = await response.json();

        if (!result.success) {
            throw new Error(result.error || '分析失败');
        }

        // 完成进度
        updateProgress(100, '分析完成！');
        
        // 优化：减少结果显示延迟，提高响应速度
        setTimeout(() => {
            currentAnalysisData = result.data;
            displayResults(result.data);

            // 自动获取推荐
            getRecommendations(result.data.video_info.bvid);

            showToast('✨ 分析完成！已生成四大板块深度报告', 'success');
        }, 200);

    } catch (error) {
        console.error('分析错误:', error);
        showError(error.message || '分析过程中出现错误，请检查链接后重试');
        showToast('分析失败：' + error.message, 'error');
    }
}

// 模拟进度更新
function simulateProgress() {
    let currentStep = 0;
    
    const updateStep = () => {
        if (currentStep < ANALYSIS_STEPS.length) {
            const step = ANALYSIS_STEPS[currentStep];
            updateProgress(step.progress, step.text);
            setStepActive(step.step);
            
            if (currentStep < ANALYSIS_STEPS.length - 1) {
                currentStep++;
                // 优化：减少延迟时间，提高响应速度
                const delay = currentStep === ANALYSIS_STEPS.length - 2 ? 4000 : 2000;
                setTimeout(updateStep, delay);
            }
        }
    };
    
    updateStep();
}

// 更新进度
function updateProgress(percent, text) {
    elements.progressBar.style.width = percent + '%';
    elements.progressText.textContent = Math.round(percent) + '%';
    elements.loadingSubtext.textContent = text;
}

// 设置步骤状态
function setStepActive(stepNumber) {
    document.querySelectorAll('.step').forEach(step => {
        const num = parseInt(step.dataset.step);
        step.classList.remove('active', 'completed');
        
        if (num < stepNumber) {
            step.classList.add('completed');
        } else if (num === stepNumber) {
            step.classList.add('active');
        }
    });
}

// 显示加载状态
function showLoading() {
    elements.loadingSection.classList.remove('hidden');
    elements.resultSection.classList.add('hidden');
    elements.errorSection.classList.add('hidden');
    elements.analyzeBtn.disabled = true;
    elements.progressBar.style.width = '0%';
    elements.progressText.textContent = '0%';
    
    // 重置步骤状态
    document.querySelectorAll('.step').forEach(step => {
        step.classList.remove('active', 'completed');
    });
}

// 隐藏加载状态
function hideLoading() {
    elements.loadingSection.classList.add('hidden');
    elements.analyzeBtn.disabled = false;
}

// 显示错误
function showError(message) {
    hideLoading();
    elements.errorSection.classList.remove('hidden');
    elements.errorMessage.textContent = message;
}

// 显示结果
function displayResults(data) {
    hideLoading();
    
    // 显示视频信息
    const videoInfo = data.video_info;
    const stats = data.stats || {};
    
    // 使用图片代理来避免防盗链
    if (videoInfo.cover) {
        elements.videoCover.src = `${API_BASE}/api/image-proxy?url=${encodeURIComponent(videoInfo.cover)}`;
        // 添加错误处理
        elements.videoCover.onerror = function() {
            this.src = '';
        };
        // 添加点击跳转功能
        elements.videoCover.style.cursor = 'pointer';
        elements.videoCover.onclick = function() {
            window.open(`https://www.bilibili.com/video/${videoInfo.bvid}`, '_blank');
            showToast('正在打开视频页面...', 'info');
        };
    } else {
        elements.videoCover.src = '';
    }
    elements.videoTitle.textContent = videoInfo.title || '未知标题';
    // 添加标题点击跳转功能
    elements.videoTitle.style.cursor = 'pointer';
    elements.videoTitle.onclick = function() {
        window.open(`https://www.bilibili.com/video/${videoInfo.bvid}`, '_blank');
        showToast('正在打开视频页面...', 'info');
    };
    elements.videoAuthor.textContent = videoInfo.author || '未知UP主';
    elements.videoView.textContent = formatNumber(videoInfo.view || 0);
    elements.videoLike.textContent = formatNumber(videoInfo.like || 0);
    elements.videoCoin.textContent = formatNumber(stats.coin || 0);
    elements.videoDuration.textContent = formatDuration(videoInfo.duration || 0);
    
    // 显示数据统计
    elements.danmakuCount.textContent = formatNumber(data.danmaku_count || 0);
    elements.commentCount.textContent = formatNumber(data.comment_count || 0);
    
    // 显示徽章
    if (data.has_subtitle) {
        elements.badgeSubtitle.textContent = '✓ 有字幕';
        elements.badgeSubtitle.style.display = 'inline-block';
    } else {
        elements.badgeSubtitle.style.display = 'none';
    }
    
    if (data.frame_count > 0) {
        elements.badgeFrames.textContent = `${data.frame_count} 帧画面`;
        elements.badgeFrames.style.display = 'inline-block';
    } else {
        elements.badgeFrames.style.display = 'none';
    }
    
    // 解析并显示分析内容
    const analysis = data.analysis;
    console.log('[调试] 原始分析内容长度:', analysis.length);

    if (typeof marked !== 'undefined') {
        try {
            // 使用改进的解析方法
            const sections = parseAnalysisSections(analysis);

            console.log('[调试] 解析后的各板块长度:', {
                summary: sections.summary.length,
                mindmap: sections.mindmap.length,
                danmaku: sections.danmaku.length,
                evaluation: sections.evaluation.length
            });

            // 第一板块：内容总结（包含知识点解析）
            const summaryContent = sections.summary || analysis;
            elements.summaryContent.innerHTML = marked.parse(summaryContent);
            console.log('[调试] Summary板块已渲染，内容长度:', summaryContent.length);

            // 第二板块：思维导图
            const mindmapContent = sections.mindmap || extractSection(analysis, ['思维导图', '知识结构', 'mindmap']) || '暂无思维导图';
            elements.mindmapContent.innerHTML = marked.parse(mindmapContent);
            console.log('[调试] Mindmap板块已渲染，内容长度:', mindmapContent.length);

            // 第三板块：弹幕分析
            const danmakuSection = sections.danmaku || extractSection(analysis, ['弹幕', 'danmaku', '互动']) || '';
            if (danmakuSection) {
                elements.danmakuContent.innerHTML = marked.parse(danmakuSection);
                console.log('[调试] 弹幕板块已渲染，内容长度:', danmakuSection.length);
            } else {
                elements.danmakuContent.innerHTML = generateDanmakuFallback(data);
                console.log('[调试] 使用弹幕降级内容');
            }

            // 第四板块：综合评价
            const evaluationContent = sections.evaluation || extractSection(analysis, ['评价', '建议', 'evaluation', '推荐']) || '暂无评价';
            elements.evaluationContent.innerHTML = marked.parse(evaluationContent);
            console.log('[调试] 评价板块已渲染，内容长度:', evaluationContent.length);

        } catch (error) {
            console.error('[错误] 解析分析内容失败:', error);
            // 降级处理：直接显示完整内容在第一个标签页
            elements.summaryContent.innerHTML = marked.parse(analysis);
            elements.mindmapContent.innerHTML = marked.parse('### 解析错误\n\n完整内容请查看"内容总结"标签页');
            elements.danmakuContent.innerHTML = marked.parse('### 解析错误\n\n完整内容请查看"内容总结"标签页');
            elements.evaluationContent.innerHTML = marked.parse('### 解析错误\n\n完整内容请查看"内容总结"标签页');
        }
    } else {
        // 降级处理：无marked.js时
        console.log('[调试] marked.js未加载，使用纯文本显示');
        elements.summaryContent.textContent = analysis;
        elements.mindmapContent.textContent = analysis;
        elements.danmakuContent.textContent = analysis;
        elements.evaluationContent.textContent = analysis;
    }
    
    // 显示结果区域
    elements.resultSection.classList.remove('hidden');

    // 生成词云
    if (data.danmaku_preview && data.danmaku_preview.length > 0) {
        generateWordcloud(data.danmaku_preview);
    }

    // 平滑滚动到结果区域
    elements.resultSection.scrollIntoView({ behavior: 'smooth', block: 'start' });
}

// 解析分析报告的各个部分
function parseAnalysisSections(text) {
    const sections = {
        summary: '',
        mindmap: '',
        danmaku: '',
        evaluation: ''
    };

    console.log('[调试] 开始解析分析内容，总长度:', text.length);

    // 使用更精确的正则表达式匹配四大板块标题
    const sectionPatterns = [
        {
            name: 'summary',
            patterns: [
                /##\s*📋\s*第一板块[：:]\s*内容深度总结与分析/,
                /##\s*第一板块[：:]\s*内容深度总结与分析/,
                /第一板块.*内容深度总结/
            ]
        },
        {
            name: 'mindmap',
            patterns: [
                /##\s*🗺️\s*第二板块[：:]\s*知识结构思维导图/,
                /##\s*第二板块[：:]\s*知识结构思维导图/,
                /第二板块.*知识结构思维导图/,
                /第二板块.*思维导图/
            ]
        },
        {
            name: 'danmaku',
            patterns: [
                /##\s*💬\s*第三板块[：:]\s*弹幕互动分析/,
                /##\s*第三板块[：:]\s*弹幕互动分析/,
                /第三板块.*弹幕互动分析/,
                /第三板块.*弹幕/
            ]
        },
        {
            name: 'evaluation',
            patterns: [
                /##\s*🌟\s*第四板块[：:]\s*综合评价与建议/,
                /##\s*第四板块[：:]\s*综合评价与建议/,
                /第四板块.*综合评价与建议/,
                /第四板块.*综合评价/
            ]
        }
    ];

    // 找到所有板块的起始位置
    const sectionPositions = [];
    for (const section of sectionPatterns) {
        for (const pattern of section.patterns) {
            const match = text.match(pattern);
            if (match) {
                sectionPositions.push({
                    name: section.name,
                    index: match.index,
                    pattern: pattern
                });
                break; // 找到第一个匹配就停止
            }
        }
    }

    // 按位置排序
    sectionPositions.sort((a, b) => a.index - b.index);

    console.log('[调试] 找到的板块位置:', sectionPositions);

    // 如果没有找到任何板块，将全文作为summary
    if (sectionPositions.length === 0) {
        console.log('[调试] 未找到板块标题，将全文作为summary');
        sections.summary = text;
        return sections;
    }

    // 提取各板块内容
    for (let i = 0; i < sectionPositions.length; i++) {
        const currentSection = sectionPositions[i];
        const startIndex = currentSection.index;
        let endIndex = text.length;

        // 找到下一个板块的起始位置作为结束位置
        if (i < sectionPositions.length - 1) {
            endIndex = sectionPositions[i + 1].index;
        }

        const sectionContent = text.substring(startIndex, endIndex).trim();
        sections[currentSection.name] = sectionContent;

        console.log(`[调试] 板块 ${currentSection.name}:`, {
            startIndex,
            endIndex,
            length: sectionContent.length
        });
    }

    // 确保每个板块都有内容，即使为空字符串
    for (const sectionName in sections) {
        if (!sections[sectionName]) {
            sections[sectionName] = '';
        }
    }

    console.log('[调试] 解析完成，各板块长度:', {
        summary: sections.summary.length,
        mindmap: sections.mindmap.length,
        danmaku: sections.danmaku.length,
        evaluation: sections.evaluation.length
    });

    return sections;
}

// 提取特定部分
function extractSection(text, keywords) {
    const lines = text.split('\n');
    let startIndex = -1;
    let endIndex = lines.length;
    
    // 查找起始位置
    for (let i = 0; i < lines.length; i++) {
        const line = lines[i].toLowerCase();
        if (keywords.some(keyword => line.includes(keyword.toLowerCase()))) {
            startIndex = i;
            break;
        }
    }
    
    if (startIndex === -1) return null;
    
    // 查找结束位置（下一个大标题）
    for (let i = startIndex + 1; i < lines.length; i++) {
        const line = lines[i];
        if ((line.startsWith('##') || line.startsWith('# ')) && 
            !keywords.some(kw => line.toLowerCase().includes(kw.toLowerCase()))) {
            endIndex = i;
            break;
        }
    }
    
    return lines.slice(startIndex, endIndex).join('\n');
}

// 生成弹幕分析降级内容
function generateDanmakuFallback(data) {
    if (!data.danmaku_preview || data.danmaku_preview.length === 0) {
        return '<p class="text-secondary">暂无弹幕数据</p>';
    }
    
    let html = '<h2>💬 弹幕互动预览</h2>';
    html += `<p>共获取到 <strong>${data.danmaku_count}</strong> 条弹幕</p>`;
    html += '<h3>热门弹幕：</h3><ul>';
    
    data.danmaku_preview.forEach((dm, idx) => {
        html += `<li>${dm}</li>`;
    });
    
    html += '</ul>';
    return html;
}

// 切换标签页
function switchTab(tabName) {
    // 更新标签按钮状态
    document.querySelectorAll('.tab-btn').forEach(btn => {
        btn.classList.remove('active');
    });
    document.querySelector(`[data-tab="${tabName}"]`).classList.add('active');

    // 显示对应内容
    document.querySelectorAll('.tab-pane').forEach(pane => {
        pane.classList.remove('active');
    });
    document.getElementById(`${tabName}Tab`).classList.add('active');
}

// 重置到输入状态
function resetToInput() {
    elements.resultSection.classList.add('hidden');
    elements.errorSection.classList.add('hidden');
    elements.videoUrl.value = '';
    elements.videoUrl.focus();
    currentAnalysisData = null;
}

// 复制到剪贴板
async function copyToClipboard() {
    if (!currentAnalysisData) return;

    const text = currentAnalysisData.analysis;
    
    try {
        await navigator.clipboard.writeText(text);
        showToast('已复制到剪贴板 📋', 'success');
    } catch (error) {
        // 降级方案
        const textarea = document.createElement('textarea');
        textarea.value = text;
        textarea.style.position = 'fixed';
        textarea.style.opacity = '0';
        document.body.appendChild(textarea);
        textarea.select();
        document.execCommand('copy');
        document.body.removeChild(textarea);
        showToast('已复制到剪贴板 📋', 'success');
    }
}

// 下载报告
function downloadReport() {
    if (!currentAnalysisData) return;

    const videoInfo = currentAnalysisData.video_info;
    const analysis = currentAnalysisData.analysis;
    
    // 创建完整的Markdown文件内容
    const content = `# ${videoInfo.title}

> BiliBili视频深度分析报告

---

## 📺 视频信息

- **标题**: ${videoInfo.title}
- **UP主**: ${videoInfo.author}
- **BV号**: ${videoInfo.bvid}
- **链接**: https://www.bilibili.com/video/${videoInfo.bvid}
- **播放量**: ${formatNumber(videoInfo.view)}
- **点赞数**: ${formatNumber(videoInfo.like)}
- **时长**: ${formatDuration(videoInfo.duration)}

---

${analysis}

---

*报告生成时间: ${new Date().toLocaleString('zh-CN')}*
*生成工具: BiliBili视频智能分析系统*
`;

    // 创建下载
    const blob = new Blob([content], { type: 'text/markdown;charset=utf-8' });
    const url = URL.createObjectURL(blob);
    const a = document.createElement('a');
    a.href = url;
    const filename = `${videoInfo.title.replace(/[<>:"/\\|?*]/g, '_')}_深度分析.md`;
    a.download = filename;
    document.body.appendChild(a);
    a.click();
    document.body.removeChild(a);
    URL.revokeObjectURL(url);
    
    showToast('报告下载成功 📥', 'success');
}

// 显示Toast提示
function showToast(message, type = 'info') {
    const toast = elements.toast;
    const messageSpan = toast.querySelector('.toast-message') || toast;
    
    if (messageSpan !== toast) {
        messageSpan.textContent = message;
    } else {
        toast.textContent = message;
    }
    
    toast.className = `toast ${type}`;
    toast.classList.remove('hidden');
    
    setTimeout(() => {
        toast.classList.add('hidden');
    }, 3500);
}

// 格式化数字
function formatNumber(num) {
    if (num >= 100000000) {
        return (num / 100000000).toFixed(2) + '亿';
    }
    if (num >= 10000) {
        return (num / 10000).toFixed(1) + '万';
    }
    return num.toLocaleString('zh-CN');
}

// 格式化时长
function formatDuration(seconds) {
    const hours = Math.floor(seconds / 3600);
    const minutes = Math.floor((seconds % 3600) / 60);
    const secs = seconds % 60;

    if (hours > 0) {
        return `${hours}:${minutes.toString().padStart(2, '0')}:${secs.toString().padStart(2, '0')}`;
    }
    return `${minutes}:${secs.toString().padStart(2, '0')}`;
}

// HTML转义函数，防止XSS攻击
function escapeHtml(text) {
    const div = document.createElement('div');
    div.textContent = text || '';
    return div.innerHTML;
}

// ================ 页面加载完成 ================
document.addEventListener('DOMContentLoaded', () => {
    console.log('%c🎉 BiliBili视频智能分析系统已就绪', 'color: #00A1D6; font-size: 16px; font-weight: bold;');
    console.log('%c✨ Powered by OpenAI Vision API', 'color: #FB7299; font-size: 14px;');
    elements.videoUrl.focus();

    // 检查B站登录状态
    checkLoginStatus();

    // 检查是否有URL参数
    const urlParams = new URLSearchParams(window.location.search);
    const videoUrl = urlParams.get('url');
    if (videoUrl) {
        elements.videoUrl.value = videoUrl;
        showToast('已自动填入视频链接，点击"开始分析"即可', 'info');
    }
});

// 阻止页面刷新时的警告（如果正在分析）
window.addEventListener('beforeunload', (e) => {
    if (!elements.analyzeBtn.disabled && !elements.loadingSection.classList.contains('hidden')) {
        e.preventDefault();
        e.returnValue = '分析正在进行中，确定要离开吗？';
    }
});

// ================ 新增功能函数 ================

// 获取相关推荐
async function getRecommendations(bvid) {
    try {
        const response = await fetch(`${API_BASE}/api/recommendations`, {
            method: 'POST',
            headers: {
                'Content-Type': 'application/json'
            },
            body: JSON.stringify({
                bvid: bvid,
                count: 6
            })
        });

        const result = await response.json();

        if (result.success && result.data.recommendations.length > 0) {
            displayRecommendations(result.data.recommendations);
        }
    } catch (error) {
        console.error('获取推荐失败:', error);
    }
}

// 显示推荐视频
function displayRecommendations(recommendations) {
    if (!elements.recommendationsSection || !elements.recommendationGrid) return;

    console.log('[推荐] 收到推荐数据:', recommendations.length, '个视频');

    // 数据验证和清理
    const validRecommendations = recommendations.filter(video => {
        return video && video.bvid && video.title;
    }).map(video => {
        // 确保数据完整性
        return {
            bvid: video.bvid || '',
            title: (video.title || '无标题').trim(),
            author: (video.author || video.uname || '未知UP主').trim(),
            pic: video.pic || '',
            play: parseInt(video.play || video.view || 0),
            like: parseInt(video.like || video.likes || 0),
            duration: parseInt(video.duration || 0)
        };
    });

    if (validRecommendations.length === 0) {
        console.warn('[推荐] 没有有效的推荐数据');
        return;
    }

    const html = validRecommendations.map((video, index) => {
        // 安全地处理标题和作者名称，防止HTML注入
        const safeTitle = escapeHtml(video.title);
        const safeAuthor = escapeHtml(video.author);
        const videoUrl = `https://www.bilibili.com/video/${video.bvid}`;

        return `
            <div class="recommendation-card" data-bvid="${video.bvid}" data-title="${safeTitle}" data-url="${videoUrl}">
                <div class="recommendation-thumbnail-wrapper">
                    <img class="recommendation-thumbnail"
                         src="${video.pic ? `${API_BASE}/api/image-proxy?url=${encodeURIComponent(video.pic)}` : ''}"
                         alt="${safeTitle}"
                         loading="lazy">
                    <div class="recommendation-duration">${formatDuration(video.duration)}</div>
                </div>
                <div class="recommendation-info">
                    <h3 class="recommendation-title" title="${safeTitle}">${safeTitle}</h3>
                    <div class="recommendation-meta">
                        <span class="recommendation-author" title="${safeAuthor}">
                            <i class="fas fa-user-circle"></i> ${safeAuthor}
                        </span>
                        <div class="recommendation-stats">
                            <span class="stat-item">
                                <i class="fas fa-play"></i> ${formatNumber(video.play)}
                            </span>
                            <span class="stat-item">
                                <i class="fas fa-thumbs-up"></i> ${formatNumber(video.like)}
                            </span>
                        </div>
                    </div>
                </div>
                <div class="recommendation-actions">
                    <button class="rec-action-btn analyze-btn"
                            onclick="analyzeRecommendation('${video.bvid}')"
                            title="分析此视频">
                        <i class="fas fa-magic"></i>
                        <span>分析</span>
                    </button>
                    <button class="rec-action-btn watch-btn"
                            onclick="watchRecommendation('${video.bvid}')"
                            title="观看原视频">
                        <i class="fas fa-play-circle"></i>
                        <span>观看</span>
                    </button>
                </div>
            </div>
        `;
    }).join('');

    elements.recommendationGrid.innerHTML = html;
    elements.recommendationsSection.classList.remove('hidden');

    console.log('[推荐] 推荐视频渲染完成:', validRecommendations.length, '个视频');

    // 为推荐卡片添加双击事件 - 默认分析
    document.querySelectorAll('.recommendation-card').forEach(card => {
        card.addEventListener('dblclick', (e) => {
            const bvid = card.dataset.bvid;
            analyzeRecommendation(bvid);
        });
    });

    // 添加右键菜单
    document.querySelectorAll('.recommendation-card').forEach(card => {
        card.addEventListener('contextmenu', (e) => {
            e.preventDefault();
            showRecommendationContextMenu(e, card);
        });
    });
}

// 分析推荐视频
function analyzeRecommendation(bvid) {
    elements.videoUrl.value = `https://www.bilibili.com/video/${bvid}`;
    elements.resultSection.scrollIntoView({ behavior: 'smooth', block: 'start' });
    handleAnalyze();
    showToast('开始分析推荐视频...', 'info');
}

// 观看推荐视频
function watchRecommendation(bvid) {
    const url = `https://www.bilibili.com/video/${bvid}`;
    window.open(url, '_blank');
    showToast('正在打开视频页面...', 'info');
}

// 显示推荐视频右键菜单
function showRecommendationContextMenu(event, card) {
    // 移除已存在的右键菜单
    const existingMenu = document.querySelector('.recommendation-context-menu');
    if (existingMenu) {
        existingMenu.remove();
    }

    // 创建右键菜单
    const contextMenu = document.createElement('div');
    contextMenu.className = 'recommendation-context-menu';
    contextMenu.innerHTML = `
        <div class="context-menu-item analyze-item" onclick="analyzeRecommendation('${card.dataset.bvid}')">
            <i class="fas fa-magic"></i> 分析视频
        </div>
        <div class="context-menu-item watch-item" onclick="watchRecommendation('${card.dataset.bvid}')">
            <i class="fas fa-play-circle"></i> 观看原视频
        </div>
        <div class="context-menu-item copy-item" onclick="copyRecommendationLink('${card.dataset.bvid}')">
            <i class="fas fa-link"></i> 复制链接
        </div>
    `;

    // 添加样式
    contextMenu.style.cssText = `
        position: fixed;
        left: ${event.pageX}px;
        top: ${event.pageY}px;
        background: white;
        border: 1px solid #ddd;
        border-radius: 8px;
        box-shadow: 0 4px 12px rgba(0,0,0,0.15);
        z-index: 10000;
        min-width: 160px;
        padding: 8px 0;
        display: block;
    `;

    // 添加到页面
    document.body.appendChild(contextMenu);

    // 点击其他地方关闭菜单
    const closeMenu = (e) => {
        if (!contextMenu.contains(e.target)) {
            contextMenu.remove();
            document.removeEventListener('click', closeMenu);
        }
    };
    setTimeout(() => {
        document.addEventListener('click', closeMenu);
    }, 100);
}

// 复制推荐视频链接
function copyRecommendationLink(bvid) {
    const url = `https://www.bilibili.com/video/${bvid}`;

    // 移除右键菜单
    const menu = document.querySelector('.recommendation-context-menu');
    if (menu) menu.remove();

    try {
        navigator.clipboard.writeText(url).then(() => {
            showToast('视频链接已复制到剪贴板 📋', 'success');
        }).catch(() => {
            // 降级方案
            const textarea = document.createElement('textarea');
            textarea.value = url;
            textarea.style.position = 'fixed';
            textarea.style.opacity = '0';
            document.body.appendChild(textarea);
            textarea.select();
            document.execCommand('copy');
            document.body.removeChild(textarea);
            showToast('视频链接已复制到剪贴板 📋', 'success');
        });
    } catch (error) {
        showToast('复制失败，请手动复制', 'error');
    }
}

// 批量分析功能
function openBatchModal() {
    if (!elements.batchModal) {
        showToast('批量分析功能暂未实现', 'info');
        return;
    }
    elements.batchModal.classList.remove('hidden');
}

function closeBatchModal() {
    if (elements.batchModal) {
        elements.batchModal.classList.add('hidden');
        if (elements.batchInput) {
            elements.batchInput.value = '';
        }
    }
}

async function startBatchAnalysis() {
    if (!elements.batchInput) return;

    const input = elements.batchInput.value.trim();
    if (!input) {
        showToast('请输入视频链接', 'error');
        return;
    }

    const bvList = input.split('\n')
        .map(line => line.trim())
        .filter(line => line.length > 0);

    if (bvList.length === 0) {
        showToast('没有有效的视频链接', 'error');
        return;
    }

    if (bvList.length > 10) {
        showToast('批量分析最多支持10个视频', 'warning');
        return;
    }

    closeBatchModal();
    showToast(`正在批量分析 ${bvList.length} 个视频，请稍候...`, 'info');

    try {
        const response = await fetch(`${API_BASE}/api/batch/analyze`, {
            method: 'POST',
            headers: {
                'Content-Type': 'application/json'
            },
            body: JSON.stringify({
                bv_list: bvList,
                analysis_type: 'summary'
            })
        });

        const result = await response.json();

        if (result.success) {
            showToast(`批量分析完成！成功分析 ${result.data.completed} 个视频`, 'success');
            // 这里可以添加显示批量结果的逻辑
        } else {
            throw new Error(result.error);
        }
    } catch (error) {
        console.error('批量分析错误:', error);
        showToast('批量分析失败：' + error.message, 'error');
    }
}

// UP主系列分析
async function analyzeSeries() {
    if (!currentAnalysisData) {
        showToast('请先分析一个视频', 'warning');
        return;
    }

    const videoInfo = currentAnalysisData.video_info;

    try {
        showToast('正在分析UP主系列信息...', 'info');

        // 这里可以调用后端的系列分析API
        // 暂时显示基本信息
        showToast(`已分析UP主 "${videoInfo.author}" 的系列信息`, 'success');

    } catch (error) {
        console.error('系列分析错误:', error);
        showToast('系列分析失败：' + error.message, 'error');
    }
}

// 模态框关闭事件
document.addEventListener('click', (e) => {
    if (e.target.classList.contains('modal')) {
        closeBatchModal();
    }
    if (e.target.classList.contains('close-btn')) {
        closeBatchModal();
    }
});

// ESC键关闭模态框
document.addEventListener('keydown', (e) => {
    if (e.key === 'Escape') {
        closeBatchModal();
        closeLoginModal();
    }
});

// ================ B站登录功能 ================

// 检查当前登录状态
async function checkLoginStatus() {
    try {
        const response = await fetch(`${API_BASE}/api/bilibili/login/check`, {
            method: 'GET',
            headers: {
                'Content-Type': 'application/json'
            }
        });

        const result = await response.json();

        if (result.success) {
            updateLoginStatusDisplay(result.data);
        } else {
            console.error('检查登录状态失败:', result.error);
            updateLoginStatusDisplay({ is_logged_in: false, user_id: null, message: '未登录' });
        }
    } catch (error) {
        console.error('检查登录状态网络错误:', error);
        updateLoginStatusDisplay({ is_logged_in: false, user_id: null, message: '检查失败' });
    }
}

// 更新登录状态显示
function updateLoginStatusDisplay(data) {
    if (!elements.loginText || !elements.loginBtn || !elements.logoutBtn) return;

    if (data.is_logged_in) {
        // 已登录状态
        elements.loginText.textContent = `已登录 (${data.user_id || '用户'})`;
        elements.loginBtn.classList.add('hidden');
        elements.logoutBtn.classList.remove('hidden');

        if (elements.loginStatus) {
            elements.loginStatus.classList.add('logged-in');
        }

        console.log('[登录] 用户已登录:', data.user_id);
        showToast('B站账号已登录，可获取完整数据', 'success');
    } else {
        // 未登录状态
        elements.loginText.textContent = data.message || '未登录';
        elements.loginBtn.classList.remove('hidden');
        elements.logoutBtn.classList.add('hidden');

        if (elements.loginStatus) {
            elements.loginStatus.classList.remove('logged-in');
        }

        console.log('[登录] 用户未登录');
    }
}

// 打开登录模态框
async function openLoginModal() {
    if (!elements.loginModal) return;

    // 清理之前的登录会话
    if (loginPollingInterval) {
        clearInterval(loginPollingInterval);
        loginPollingInterval = null;
    }

    elements.loginModal.classList.remove('hidden');

    // 重置登录状态
    resetLoginModal();

    // 开始登录流程
    await startLogin();
}

// 重置登录模态框状态
function resetLoginModal() {
    if (elements.qrSection) elements.qrSection.classList.remove('hidden');
    if (elements.qrPlaceholder) elements.qrPlaceholder.classList.remove('hidden');
    if (elements.qrCode) elements.qrCode.classList.add('hidden');
    if (elements.loginStatusSection) elements.loginStatusSection.classList.add('hidden');
    if (elements.loginSuccessSection) elements.loginSuccessSection.classList.add('hidden');

    currentLoginSession = null;
}

// 开始登录流程
async function startLogin() {
    try {
        const response = await fetch(`${API_BASE}/api/bilibili/login/start`, {
            method: 'POST',
            headers: {
                'Content-Type': 'application/json'
            }
        });

        const result = await response.json();

        if (result.success) {
            currentLoginSession = result.data.session_id;
            displayQRCode(result.data.qr_code);
            startLoginPolling();
        } else {
            throw new Error(result.error || '启动登录失败');
        }
    } catch (error) {
        console.error('启动登录失败:', error);
        showToast('启动登录失败: ' + error.message, 'error');
        closeLoginModal();
    }
}

// 显示二维码
function displayQRCode(qrCodeData) {
    if (!elements.qrPlaceholder || !elements.qrCode || !elements.qrImage) return;

    elements.qrImage.src = qrCodeData;
    elements.qrPlaceholder.classList.add('hidden');
    elements.qrCode.classList.remove('hidden');

    console.log('[登录] 二维码已显示');
}

// 开始轮询登录状态
function startLoginPolling() {
    if (!currentLoginSession || loginPollingInterval) return;

    console.log('[登录] 开始轮询登录状态');

    loginPollingInterval = setInterval(async () => {
        try {
            const response = await fetch(`${API_BASE}/api/bilibili/login/status`, {
                method: 'POST',
                headers: {
                    'Content-Type': 'application/json'
                },
                body: JSON.stringify({
                    session_id: currentLoginSession
                })
            });

            const result = await response.json();

            if (result.success) {
                handleLoginStatusUpdate(result.data);
            } else {
                console.error('检查登录状态失败:', result.error);
                showToast('检查登录状态失败', 'error');
            }
        } catch (error) {
            console.error('轮询登录状态错误:', error);
        }
    }, 2000); // 每2秒检查一次
}

// 处理登录状态更新
function handleLoginStatusUpdate(data) {
    if (!elements.loginStatusSection || !elements.statusText) return;

    switch (data.status) {
        case 'waiting':
            elements.statusText.textContent = '等待扫码...';
            break;
        case 'scanning':
            elements.statusText.textContent = '已扫码，请在手机上确认登录';
            break;
        case 'success':
            handleLoginSuccess();
            break;
        default:
            if (data.error) {
                handleLoginError(data.error);
            }
            break;
    }
}

// 处理登录成功
function handleLoginSuccess() {
    console.log('[登录] 登录成功');

    // 停止轮询
    if (loginPollingInterval) {
        clearInterval(loginPollingInterval);
        loginPollingInterval = null;
    }

    // 显示成功状态
    if (elements.qrSection) elements.qrSection.classList.add('hidden');
    if (elements.loginStatusSection) elements.loginStatusSection.classList.add('hidden');
    if (elements.loginSuccessSection) elements.loginSuccessSection.classList.remove('hidden');

    // 更新登录状态
    setTimeout(() => {
        checkLoginStatus();
        closeLoginModal();
        showToast('登录成功！已获取完整数据权限', 'success');
    }, 2000);
}

// 处理登录错误
function handleLoginError(error) {
    console.error('[登录] 登录失败:', error);

    // 停止轮询
    if (loginPollingInterval) {
        clearInterval(loginPollingInterval);
        loginPollingInterval = null;
    }

    showToast('登录失败: ' + error, 'error');

    // 显示错误状态
    if (elements.qrSection) elements.qrSection.classList.add('hidden');
    if (elements.loginStatusSection) {
        elements.loginStatusSection.classList.remove('hidden');
        if (elements.statusText) {
            elements.statusText.textContent = '登录失败：' + error;
        }
    }
}

// 刷新二维码
async function refreshQRCode() {
    console.log('[登录] 刷新二维码');
    resetLoginModal();
    await startLogin();
}

// 关闭登录模态框
function closeLoginModal() {
    if (!elements.loginModal) return;

    elements.loginModal.classList.add('hidden');

    // 清理登录会话
    if (loginPollingInterval) {
        clearInterval(loginPollingInterval);
        loginPollingInterval = null;
    }

    currentLoginSession = null;
}

// 处理登出
async function handleLogout() {
    try {
        const response = await fetch(`${API_BASE}/api/bilibili/login/logout`, {
            method: 'POST',
            headers: {
                'Content-Type': 'application/json'
            }
        });

        const result = await response.json();

        if (result.success) {
            showToast('已成功退出登录', 'success');
            // 更新登录状态显示
            updateLoginStatusDisplay({ is_logged_in: false, user_id: null, message: '未登录' });
        } else {
            throw new Error(result.error || '登出失败');
        }
    } catch (error) {
        console.error('登出失败:', error);
        showToast('登出失败: ' + error.message, 'error');
    }
}

// ================ 词云功能 ================

// 生成词云
function generateWordcloud(danmakuList) {
    if (!elements.wordcloudCanvas || !elements.wordcloudLoading) return;

    try {
        // 显示加载状态
        elements.wordcloudLoading.classList.remove('hidden');
        elements.wordcloudCanvas.style.display = 'none';

        console.log('[词云] 开始生成词云，弹幕数量:', danmakuList.length);

        // 处理弹幕文本
        const processedText = processDanmakuText(danmakuList);
        console.log('[词云] 处理后的文本长度:', processedText.length);

        // 分词并统计词频
        const wordFrequency = extractKeywords(processedText);
        console.log('[词云] 提取到的关键词数量:', Object.keys(wordFrequency).length);

        if (Object.keys(wordFrequency).length === 0) {
            throw new Error('未提取到有效关键词');
        }

        // 准备词云数据
        const wordcloudData = prepareWordcloudData(wordFrequency);
        console.log('[词云] 词云数据准备完成，词汇数量:', wordcloudData.length);

        // 设置画布尺寸
        const container = elements.wordcloudCanvas.parentElement;
        const containerWidth = container.clientWidth - 40; // 减去padding
        const canvasWidth = Math.min(containerWidth, 800);
        const canvasHeight = Math.min(canvasWidth * 0.5, 400);

        elements.wordcloudCanvas.width = canvasWidth;
        elements.wordcloudCanvas.height = canvasHeight;

        // 生成词云
        setTimeout(() => {
            // 检查WordCloud是否可用
            if (typeof WordCloud === 'undefined') {
                console.error('[词云] WordCloud库未加载');
                throw new Error('词云库未加载');
            }

            WordCloud(elements.wordcloudCanvas, {
                list: wordcloudData,
                gridSize: 16,
                weightFactor: function (size) {
                    return size * canvasWidth / 800;
                },
                fontFamily: 'Arial, "Microsoft YaHei", sans-serif',
                color: function (word, weight) {
                    // B站主题色彩
                    const colors = [
                        '#00A1D6', // B站蓝
                        '#FB7299', // B站粉
                        '#23ADE5', // 浅蓝
                        '#FF8CB8', // 浅粉
                        '#0089B8', // 深蓝
                        '#E56B9F', // 深粉
                        '#52C41A', // 成功绿
                        '#FAAD14', // 警告橙
                        '#1890FF', // 信息蓝
                        '#722ED1'  // 紫色
                    ];
                    return colors[Math.floor(Math.random() * colors.length)];
                },
                rotateRatio: 0.3,
                rotationSteps: 2,
                backgroundColor: 'transparent',
                click: function(item) {
                    if (item && item[0]) {
                        console.log('[词云] 点击词汇:', item[0]);
                        showToast(`关键词 "${item[0]}" 出现 ${item[1]} 次`, 'info');
                    }
                },
                hover: function(item, dimension, event) {
                    if (item && item[0]) {
                        elements.wordcloudCanvas.style.cursor = 'pointer';
                    } else {
                        elements.wordcloudCanvas.style.cursor = 'crosshair';
                    }
                }
            });

            // 隐藏加载状态，显示词云
            elements.wordcloudLoading.classList.add('hidden');
            elements.wordcloudCanvas.style.display = 'block';

            console.log('[词云] 词云生成完成');

        }, 500);

    } catch (error) {
        console.error('[词云] 生成词云失败:', error);
        elements.wordcloudLoading.classList.add('hidden');

        // 显示错误信息
        if (elements.wordcloudSection) {
            const errorHtml = `
                <div style="text-align: center; padding: 40px; color: var(--text-secondary);">
                    <i class="fas fa-exclamation-triangle" style="font-size: 48px; color: var(--error-color); margin-bottom: 16px; display: block;"></i>
                    <p>词云生成失败: ${error.message}</p>
                    <button class="wordcloud-btn" onclick="refreshWordcloud()" style="margin-top: 16px;">
                        <i class="fas fa-redo"></i> 重试
                    </button>
                </div>
            `;
            elements.wordcloudSection.innerHTML += errorHtml;
        }

        showToast('词云生成失败: ' + error.message, 'error');
    }
}

// 处理弹幕文本
function processDanmakuText(danmakuList) {
    if (!Array.isArray(danmakuList)) {
        console.warn('[词云] 弹幕数据不是数组格式');
        return '';
    }

    // 合并所有弹幕文本
    let allText = danmakuList.join(' ');

    // 清理文本
    allText = allText
        .replace(/\[.*?\]/g, '') // 移除方括号内容
        .replace(/https?:\/\/\S+/g, '') // 移除URL
        .replace(/[^\u4e00-\u9fa5a-zA-Z0-9\s]/g, ' ') // 只保留中文、英文、数字和空格
        .replace(/\s+/g, ' ') // 合并多个空格
        .trim();

    console.log('[词云] 文本清理完成，原始长度:', danmakuList.join(' ').length, '清理后长度:', allText.length);

    return allText;
}

// 提取关键词并统计词频
function extractKeywords(text) {
    if (!text || text.length < 10) {
        console.warn('[词云] 文本太短或为空');
        return {};
    }

    const wordFrequency = {};
    console.log('[词云] 使用简单分词算法');

    try {
        // 提取中文关键词（简单分词）
        extractChineseKeywords(text, wordFrequency);

        // 提取英文单词
        extractEnglishWords(text, wordFrequency);

    } catch (error) {
        console.error('[词云] 分词过程出错:', error);
    }

    // 过滤低频词
    const filteredFrequency = {};
    const minFrequency = Math.max(1, Math.floor(Object.keys(wordFrequency).length * 0.02)); // 至少出现1次或前2%

    for (const [word, freq] of Object.entries(wordFrequency)) {
        if (freq >= minFrequency) {
            filteredFrequency[word] = freq;
        }
    }

    console.log('[词云] 词频统计完成，总词汇:', Object.keys(wordFrequency).length, '过滤后:', Object.keys(filteredFrequency).length);

    return filteredFrequency;
}

// 判断是否为有效关键词
function isValidKeyword(word) {
    if (!word || word.length < 2) return false;

    // 过滤停用词
    const stopWords = new Set([
        '的', '了', '是', '在', '我', '有', '和', '就', '不', '人', '都', '一', '一个', '上', '也', '很', '到', '说', '要', '去', '你', '会', '着', '没有', '看', '好', '自己', '这',
        'the', 'a', 'an', 'and', 'or', 'but', 'in', 'on', 'at', 'to', 'for', 'of', 'with', 'by', 'is', 'are', 'was', 'were', 'be', 'been', 'being', 'have', 'has', 'had', 'do', 'does', 'did', 'will', 'would', 'could', 'should', 'may', 'might', 'must', 'can', 'this', 'that', 'these', 'those'
    ]);

    // 过滤纯数字和特殊字符
    if (/^\d+$/.test(word)) return false;
    if (stopWords.has(word.toLowerCase())) return false;

    // 过滤过短或过长的词
    if (word.length < 2 || word.length > 10) return false;

    return true;
}

// 提取中文关键词（简单分词）
function extractChineseKeywords(text, wordFrequency) {
    // 首先提取单个字符（但只统计高频字）
    const singleChars = {};
    for (let i = 0; i < text.length; i++) {
        const char = text[i];
        if (/^[\u4e00-\u9fa5]$/.test(char) && isValidKeyword(char)) {
            singleChars[char] = (singleChars[char] || 0) + 1;
        }
    }

    // 只保留出现3次以上的单字
    for (const [char, freq] of Object.entries(singleChars)) {
        if (freq >= 3) {
            wordFrequency[char] = (wordFrequency[char] || 0) + freq;
        }
    }

    // 提取2-4字的中文词汇
    for (let len = 2; len <= 4; len++) {
        for (let i = 0; i <= text.length - len; i++) {
            const word = text.substr(i, len);
            if (/^[\u4e00-\u9fa5]+$/.test(word) && isValidKeyword(word)) {
                wordFrequency[word] = (wordFrequency[word] || 0) + 1;
            }
        }
    }
}

// 提取英文单词
function extractEnglishWords(text, wordFrequency) {
    const englishWords = text.match(/[a-zA-Z]+/g) || [];
    for (const word of englishWords) {
        const lowerWord = word.toLowerCase();
        if (lowerWord.length >= 3 && isValidKeyword(lowerWord)) {
            wordFrequency[lowerWord] = (wordFrequency[lowerWord] || 0) + 1;
        }
    }
}

// 准备词云数据
function prepareWordcloudData(wordFrequency) {
    // 按词频排序
    const sortedWords = Object.entries(wordFrequency)
        .sort((a, b) => b[1] - a[1])
        .slice(0, 100); // 限制最多100个词

    // 转换为WordCloud2.js需要的格式
    const wordcloudData = sortedWords.map(([word, freq]) => {
        // 计算权重（基于词频的对数缩放）
        const weight = Math.max(12, Math.min(60, Math.log(freq + 1) * 15));
        return [word, weight];
    });

    console.log('[词云] 词云数据准备完成，词汇数:', wordcloudData.length);
    return wordcloudData;
}

// 刷新词云
function refreshWordcloud() {
    if (!currentAnalysisData || !currentAnalysisData.danmaku_preview) {
        showToast('没有可用的弹幕数据', 'warning');
        return;
    }

    console.log('[词云] 刷新词云');
    generateWordcloud(currentAnalysisData.danmaku_preview);
    showToast('词云已刷新', 'success');
}

// 下载词云
function downloadWordcloud() {
    if (!elements.wordcloudCanvas) {
        showToast('词云画布不存在', 'error');
        return;
    }

    try {
        // 检查画布是否有内容
        const ctx = elements.wordcloudCanvas.getContext('2d');
        if (!ctx) {
            showToast('无法获取画布内容', 'error');
            return;
        }

        // 转换为图片并下载
        elements.wordcloudCanvas.toBlob((blob) => {
            if (!blob) {
                showToast('生成图片失败', 'error');
                return;
            }

            const url = URL.createObjectURL(blob);
            const a = document.createElement('a');
            a.href = url;

            const videoTitle = currentAnalysisData?.video_info?.title || '弹幕词云';
            const filename = `${videoTitle.replace(/[<>:"/\\|?*]/g, '_')}_弹幕词云.png`;
            a.download = filename;

            document.body.appendChild(a);
            a.click();
            document.body.removeChild(a);
            URL.revokeObjectURL(url);

            showToast('词云图片下载成功 📥', 'success');
        }, 'image/png');

    } catch (error) {
        console.error('[词云] 下载词云失败:', error);
        showToast('下载词云失败: ' + error.message, 'error');
    }
}
